package org.ltc.alliance.service.power;

import org.ltc.alliance.constant.ErrorConst;
import org.ltc.alliance.constant.PowerConst;
import org.ltc.alliance.dao.PowerDao;
import org.ltc.alliance.exception.BusinessException;
import org.ltc.alliance.model.PowerDomain;
import org.ltc.alliance.service.club.ClubService;
import org.ltc.alliance.service.clubuser.ClubUserService;
import org.ltc.alliance.service.user.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.Iterator;
import java.util.List;

@Service
public class PowerServiceImpl implements PowerService{

    @Autowired
    PowerDao powerDao;
    @Autowired
    ClubService clubService;
    @Autowired
    UserService userService;
    @Autowired
    ClubUserService clubUserService;

    @Override
    public void grantManager(Integer provider, Integer receiver, Integer cid) {
        clubUserService.userInClub(cid, provider);
        clubUserService.userInClub(cid, receiver);
        this.powerReleaser(provider, cid);

        PowerDomain powerDomain = new PowerDomain();
        powerDomain.setPower(PowerConst.MANAGER);
        powerDomain.setCid(cid);
        powerDomain.setUid(receiver);

        if (this.powerExist(receiver, cid)) {
            powerDao.alterPower(powerDomain);
        } else {
            powerDao.savePowerInfo(powerDomain);
        }
    }

    @Override
    public void InitReleaser(Integer releaser, Integer cid) {
        PowerDomain powerDomain = new PowerDomain();
        powerDomain.setPower(PowerConst.RELEASER);
        powerDomain.setCid(cid);
        powerDomain.setUid(releaser);

        powerDao.savePowerInfo(powerDomain);
    }

    @Override
    public void transferReleaser(Integer provider, Integer receiver, Integer cid) {
        clubUserService.userInClub(cid, provider);
        clubUserService.userInClub(cid, receiver);
        this.powerReleaser(provider, cid);

        PowerDomain powerDomain = new PowerDomain();
        powerDomain.setPower(PowerConst.RELEASER);
        powerDomain.setCid(cid);
        powerDomain.setUid(receiver);

        if (this.powerExist(receiver, cid)) {
            powerDao.alterPower(powerDomain);
        } else {
            powerDao.savePowerInfo(powerDomain);
        }
        this.revokeManager(receiver,provider,cid);
    }

    @Override
    public void revokeManager(Integer provider, Integer receiver, Integer cid) {
        clubUserService.userInClub(cid, provider);
        clubUserService.userInClub(cid, receiver);
        this.powerReleaser(provider, cid);

        PowerDomain powerDomain = new PowerDomain();
        powerDomain.setPower(PowerConst.NORMAL);
        powerDomain.setCid(cid);
        powerDomain.setUid(receiver);

        if (!this.powerExist(receiver, cid)) {
            throw new BusinessException(ErrorConst.Power.POWER_NOT_EXIST);
        }
        powerDao.alterPower(powerDomain);
    }

    @Override
    public PowerConst getPower(Integer uid, Integer cid) {
        return powerDao.getPowerByUidAndCid(uid, cid);
    }

    @Override
    public List<PowerDomain> getPowerDomainListByUid(Integer uid) {
        List<PowerDomain> powers = powerDao.getPowerDomainListByUid(uid);
        Iterator<PowerDomain> iterator = powers.iterator();
        while (iterator.hasNext()) {
            PowerDomain power = (PowerDomain) iterator.next();
            if (power.getPower().equals(PowerConst.NORMAL)) {
                iterator.remove();
            }
        }
        return powers;
    }

    @Override
    public List<PowerDomain> getPowerDomainListByCid(Integer cid) {
        List<PowerDomain> powers = powerDao.getPowerDomainListByCid(cid);
        Iterator<PowerDomain> iterator = powers.iterator();
        while (iterator.hasNext()) {
            PowerDomain power = (PowerDomain) iterator.next();
            if (power.getPower().equals(PowerConst.NORMAL)) {
                iterator.remove();
            }
        }
        return powers;
    }

    @Override
    public void powerReleaser(Integer uid, Integer cid) {
        PowerConst powerConst = powerDao.getPowerByUidAndCid(uid, cid);
        if (!powerConst.equals(PowerConst.RELEASER)){
            throw new BusinessException(ErrorConst.Power.POWER_NOT_RELEASER);
        }
    }

    @Override
    public void powerManager(Integer uid, Integer cid) {
        PowerConst powerConst = powerDao.getPowerByUidAndCid(uid, cid);
        if (!powerConst.equals(PowerConst.MANAGER)){
            throw new BusinessException(ErrorConst.Power.POWER_NOT_MANAGER);
        }
    }

    @Override
    public void powerOverManager(Integer uid, Integer cid) {
        PowerConst powerConst = powerDao.getPowerByUidAndCid(uid, cid);
        if (powerConst != null) {
            if (!powerConst.equals(PowerConst.NORMAL)) {
                return;
            }
        }
        throw new BusinessException(ErrorConst.Power.POWER_NORMAL);
    }

    @Override
    public Boolean powerExist(Integer uid, Integer cid) {
        PowerDomain powerExist = powerDao.getPowerDomainByUidAndCid(uid, cid);
        return null != powerExist;

    }
}
